home *** CD-ROM | disk | FTP | other *** search
/ Celestin Apprentice 2 / Apprentice-Release2.iso / Tools / Languages / Harvest C 1.3 / Source Code / lex2.c < prev    next >
Encoding:
C/C++ Source or Header  |  1992-06-15  |  5.5 KB  |  248 lines  |  [TEXT/ALFA]

  1. /*
  2.     Harvest C
  3.     Copyright 1992 Eric W. Sink.  All rights reserved.
  4.     
  5.     This file is part of Harvest C.
  6.     
  7.     Harvest C is free software; you can redistribute it and/or modify
  8.     it under the terms of the GNU Generic Public License as published by
  9.     the Free Software Foundation; either version 2, or (at your option)
  10.     any later version.
  11.     
  12.     Harvest C is distributed in the hope that it will be useful,
  13.     but WITHOUT ANY WARRANTY; without even the implied warranty of
  14.     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  15.     GNU General Public License for more details.
  16.     
  17.     You should have received a copy of the GNU General Public License
  18.     along with Harvest C; see the file COPYING.  If not, write to
  19.     the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
  20.     
  21.     Harvest C is not in any way a product of the Free Software Foundation.
  22.     Harvest C is not GNU software.
  23.     Harvest C is not public domain.
  24.  
  25.     This file may have other copyrights which are applicable as well.
  26.  
  27. */
  28.  
  29. /*
  30.  * Harvest C
  31.  * 
  32.  * Copyright 1991 Eric W. Sink   All rights reserved.
  33.  * 
  34.  * This file contains parts of the lexical scanner.
  35.  * 
  36.  * 
  37.  */
  38.  
  39.  
  40. #include "conditcomp.h"
  41. #include <stdio.h>
  42. #include <ctype.h>
  43. #include <string.h>
  44. #include "structs.h"
  45.  
  46. #pragma segment Lex2
  47.  
  48. PPSYMVia_t
  49. isDefined(char *name)
  50. {
  51.     PPSYMVia_t                      found;
  52.     found = PPTableSearch(Defines, name);
  53.     if (found) {
  54.     if (GetPPSymFlags(found) & PREPROCUNDEF) {
  55.         return 0;
  56.     } else {
  57.         return found;
  58.     }
  59.     } else {
  60.     return 0;
  61.     }
  62.     return found;
  63. }
  64.  
  65. PPSYMVia_t
  66. AddDefine(char *name, EString_t value)
  67. /*
  68.  * This routine adds a #define symbol to the Preprocessor Defines list.  Note
  69.  * that all #define symbols, including macros in the routine above, are
  70.  * inserted at the front of the list.
  71.  */
  72. {
  73.     PPSYMVia_t                      tmp;
  74. #ifdef Undefined
  75.     tmp = PPTableSearch(Defines, name);
  76.     if (tmp) {
  77.     UserWarning2(WARN_preprocredef, name);
  78.     if (GetPPSymFlags(tmp) & PREPROCLOCKED) {
  79.         return tmp;
  80.     }
  81.     tmp = PPTableRemove(Defines, name);
  82.     }
  83. #endif
  84.     PreprocSymbolCount++;
  85.     tmp = PPTableAdd(Defines, name);
  86.     SetPPSymValue(tmp, value);
  87.     return tmp;
  88. }
  89.  
  90. PPSYMVia_t
  91. AddMacroFunc(char *name, int NumArgs, EString_t value, SymListVia_t ParmNames)
  92. /*
  93.  * This function adds a #define macro with parameters to the PreProcessor
  94.  * macro list.  See the data structure definition for the macro structure for
  95.  * explanations of the fields.
  96.  */
  97. {
  98.     PPSYMVia_t                      tmp;
  99.     tmp = AddDefine(name, value);
  100.     if (tmp) {
  101.     SetPPSymArgCount(tmp, NumArgs);
  102.     SetPPSymArgs(tmp, ParmNames);
  103.     }
  104.     return tmp;
  105. }
  106.  
  107. PPSYMVia_t
  108. UnDefine(char *name)
  109. {
  110.     PPSYMVia_t                      found;
  111.     found = PPTableSearch(Defines, name);
  112.     if (found) {
  113.     if (GetPPSymFlags(found) & PREPROCLOCKED) {
  114.         return found;
  115.     } else {
  116.         return PPTableRemove(Defines, found);
  117.     }
  118.     } else {
  119.     return 0;
  120.     }
  121.     return found;
  122. }
  123.  
  124. /*
  125.  * The PPStatus is used by the PreProcessor to determine when code should be
  126.  * ignored or not.  When an #ifdef fails, PPStatus is set to true.  Whenever
  127.  * PPStatus is true, the parser ignores the tokens it reads.  A stack is used
  128.  * to keep track of nested #if type preprocessor commands.
  129.  */
  130.  
  131. void
  132. SetPPStatus(int stat)
  133. /* Actually this is a stack push */
  134. {
  135.     PreprocStack[PPSP++] = PPStatus;
  136.     PPStatus = stat;
  137. }
  138.  
  139. void
  140. GetPPStatus(void)
  141. /* Actually this is a stack pop */
  142. {
  143.     PPStatus = PreprocStack[--PPSP];
  144. }
  145.  
  146. int
  147. hexvalue(char c)
  148. /* Returns the integer value of the hex digit passed. */
  149. {
  150.     if ((c >= '0') && (c <= '9')) {
  151.     return c - '0';
  152.     } else if ((c >= 'a') && (c <= 'f')) {
  153.     return c - 'a' + 10;
  154.     } else if ((c >= 'A') && (c <= 'F')) {
  155.     return c - 'A' + 10;
  156.     } else {
  157.     VeryBadParseError("hexvalue() was passed a non-hex character");
  158.     }
  159.     return 0;
  160. }
  161.  
  162. int
  163. ishexdigit(char c)
  164. /* Returns true iff the arg is a valid hex digit. */
  165. {
  166.     return (((c >= '0') && (c <= '9')) || ((c >= 'a') && (c <= 'f')) ||
  167.         ((c >= 'A') && (c <= 'F')));
  168. }
  169.  
  170. int
  171. isoctaldigit(char c)
  172. /*
  173.  * Returns true iff the arg is a valid octal digit.  Note that, in accordance
  174.  * with ANSI, 8 and 9 are not valid octal digits.
  175.  */
  176. {
  177.     return (((c >= '0') && (c <= '7')));
  178. }
  179.  
  180. SYMVia_t
  181. isTypedefName(char *name)
  182. {
  183.     SYMVia_t                        result;
  184.     result = TableSearch(TP_defnames, (name));
  185.     if (result) {
  186.     if (LookUpSymbol(name)) {
  187.         result = NULL;
  188.     }
  189.     }
  190.     return result;
  191. }
  192.  
  193. int
  194. isFirstIDChar(char c)
  195. {
  196.     /* Legal characters to begin an identifier are [a-zA-Z_] */
  197.     if ((c >= 'a' && c <= 'z') || (c >= 'A' && c <= 'Z') || c ==
  198.     '_')
  199.     return 1;
  200.     else
  201.     return 0;
  202. }
  203.  
  204. int
  205. isAnyIDChar(char c)
  206. {
  207.     /*
  208.      * After the first character, an identifer may include digits.
  209.      */
  210.     return (isdigit(c) || isFirstIDChar(c));
  211. }
  212.  
  213. int
  214. isKeyword(char *toke)
  215. /*
  216.  * This routine uses a hash table for searching.  Note that the keyword
  217.  * "defined" is special.  It is NOT a C keyword.  It is implemented as a
  218.  * keyword, but is only valid during #if expressions. The only keyword
  219.  * addition to the C language is "pascal" also "inline"
  220.  */
  221. {
  222.     int                             ndx;
  223.     int                             base;
  224.     int                             done;
  225.     ndx = KWHash(toke);
  226.     base = ndx;
  227.     done = 0;
  228.     while (!done) {
  229.     if (KWTable[ndx].val) {
  230.         if (!strcmp(KWTable[ndx].name, toke)) {
  231.         if (KWTable[ndx].val == DEFINED) {
  232.             if (InPreprocIf) {
  233.             return DEFINED;
  234.             } else {
  235.             return 0;
  236.             }
  237.         } else {
  238.             return KWTable[ndx].val;
  239.         }
  240.         } else {
  241.         ndx = (ndx + base) % KEYWORDTABLESIZE;
  242.         }
  243.     } else
  244.         done = 1;
  245.     }
  246.     return 0;
  247. }
  248.